﻿/***************************************************************
 * 开发人员：网魂小兵@http://www.mozlite.com
 * 
 * 单向加密方法类。
 * 
 * 最后修改：2011-10-25
 * ************************************************************/
namespace Mozlite.Cryptography
{
    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Security.Cryptography;
    using System.IO;
    using System.Globalization;
    /// <summary>
    /// 加密解密管理类。
    /// </summary>
    public class Cryptors
    {
        private Cryptors() { }

        private static HashAlgorithm Create(EncryptionAlgorithm type)
        {
            if (type <= EncryptionAlgorithm.Clear || type >= EncryptionAlgorithm.Des)
                throw new Exception("It is not HashAlgorithm type!");
            switch (type) {
                case EncryptionAlgorithm.SHA1:
                    return new SHA1CryptoServiceProvider();
                case EncryptionAlgorithm.SHA256:
                    return new SHA256Managed();
                case EncryptionAlgorithm.SHA512:
                    return new SHA512Managed();
            }
            return new MD5CryptoServiceProvider();
        }
        /// <summary>
        /// 单向加密流，并返回加密后字节。
        /// </summary>
        /// <param name="stream">用于加密的流。</param>
        /// <param name="type">加密类型。</param>
        /// <returns>返回加密后的二进制字节。</returns>
        public static byte[] Make(Stream stream, EncryptionAlgorithm type)
        {
            HashAlgorithm transform = Create(type);
            transform.Initialize();
            transform.ComputeHash(stream);
            byte[] hash = transform.Hash;
            transform.Clear();
            return hash;
        }
        /// <summary>
        /// 单向加密文件，并返回加密后字节。
        /// </summary>
        /// <param name="fileName">文件物理路径。</param>
        /// <param name="type">加密类型。</param>
        /// <returns>返回加密后的二进制字节。</returns>
        public static byte[] BatchMake(string fileName, EncryptionAlgorithm type)
        {
            FileStream stream = System.IO.File.Open(fileName, FileMode.Open, FileAccess.Read);
            byte[] buffer = Cryptors.BatchMake(stream, type);
            stream.Close();
            return buffer;
        }
        /// <summary>
        /// 单向加密流(大字节流)，并返回加密后字节。
        /// </summary>
        /// <param name="stream">用于加密的流。</param>
        /// <param name="type">加密类型。</param>
        /// <returns>返回加密后的二进制字节。</returns>
        public static byte[] BatchMake(Stream stream, EncryptionAlgorithm type)
        {
            HashAlgorithm transform = Create(type);
            transform.Initialize();
            long lenth = stream.Length;
            stream.Seek(0, SeekOrigin.Begin);
            byte[] buffer=new byte[2048];
            while (lenth > 0L) {
                int count = (lenth >= 2048 ? 2048 : (int)lenth);
                stream.Read(buffer, 0, count);
                lenth -= count;
                if (lenth == 0)
                    transform.TransformFinalBlock(buffer, 0, count);
                else
                    transform.TransformBlock(buffer, 0, count, buffer, 0);
            }
            byte[] hash = transform.Hash;
            transform.Clear();
            return hash;
        }
        /// <summary>
        /// 单向加二进制字节，并返回加密后字节。
        /// </summary>
        /// <param name="buffer">用于加密的流。</param>
        /// <param name="type">加密类型。</param>
        /// <returns>返回加密后的二进制字节。</returns>
        public static byte[] Make(byte[] buffer, EncryptionAlgorithm type)
        {
            HashAlgorithm transform = Create(type);
            transform.Initialize();
            transform.ComputeHash(buffer);
            byte[] hash = transform.Hash;
            transform.Clear();
            return hash;
        }
        /// <summary>
        /// 单向加密文本字符串，并返回加密后字节。
        /// </summary>
        /// <param name="text">用于加密的流。</param>
        /// <param name="type">加密类型。</param>
        /// <returns>返回加密后的二进制字节。</returns>
        public static byte[] Make(string text, EncryptionAlgorithm type)
        {
            return Make(Encoding.Default.GetBytes(text), type);
        }
    }
}
